from datetime import datetime
import os

from django.conf import settings
from rest_framework.viewsets import ModelViewSet
from rest_framework import permissions, status
from rest_framework.decorators import action
from rest_framework.response import Response

from envs.models import Envs
from projects import serializers
from projects.models import Projects
from projects.utils import get_count_by_project
from modulars.models import Modulars
from testcases.models import Testcases
from configures.models import Configures
from utils import common


class ProjectsViewSet(ModelViewSet):
    """
    list:
    返回项目(多个)列表数据

    create:
    创建项目

    retrieve:
    返回项目(单个)详情数据

    update:
    更新(全部)项目

    partial_update:
    更新(部分)项目

    destroy:
    删除项目

    names:
    获取所有项目ID和名称

    modulars:
    获取指定项目的所有模块数据

    pcase:
    获取指定项目下的所有用例

    configures:
    获取指定项目下的所有配置
    """
    queryset = Projects.objects.filter(is_delete=False)
    serializer_class = serializers.ProjectModelSerializer
    ordering_fields = ['id', 'name']
    permission_classes = [permissions.IsAuthenticated]

    def perform_destroy(self, instance):
        instance.is_delete = True
        instance.save()     #逻辑删除

    @action(methods=['get'], detail=False)
    def names(self, request, *args, **kwargs):
        queryset = self.get_queryset()
        serializer = self.get_serializer(instance=queryset, many=True)
        return Response(serializer.data)


    @action(methods=['get'], detail=True)
    def modulars(self, request, pk=None):
        modulars_objs = Modulars.objects.filter(project_id=pk, is_delete=False)
        one_list = []
        for obj in modulars_objs:
            one_list.append({
                'id': obj.id,
                'name': obj.name
            })
        return Response(data=one_list)

    @action(methods=['get'], detail=True)
    def pcase(self, request, pk=None):
        modula_objs = Modulars.objects.filter(is_delete=False, project=pk)
        if not modula_objs.exists():
            data_dict = {
                'detail': '此项目下无功能'
            }
            return Response(data_dict, status=status.HTTP_400_BAD_REQUEST)
        one_list = []
        for m_obj in modula_objs:
            testcase_objs = Testcases.objects.filter(is_delete=False, modular=m_obj)
            for obj in testcase_objs:
                one_list.append({
                    'id': obj.id,
                    'name': obj.name
                })
        return Response(data=one_list)

    @action(methods=['get'], detail=True)
    def configures(self, request, pk=None):
        configures_obj = Configures.objects.filter(project_id=pk, is_delete=False)
        one_list = []
        for obj in configures_obj:
            one_list.append({
                'id': obj.id,
                'name': obj.name
            })
        return Response(data=one_list)

    def list(self, request, *args, **kwargs):
        response = super().list(request, *args, **kwargs)
        response.data['results'] = get_count_by_project(response.data['results'])
        return response

    @action(methods=['post'], detail=True)
    def run(self, request, pk=None):
        instance = self.get_object()
        serializer = self.get_serializer(instance, data=request.data)
        serializer.is_valid(raise_exception=True)
        datas = serializer.validated_data
        # 获取环境变量ID
        env_id = datas.get('env_id')

        # 创建测试用例所在的目录名
        testcase_dir_path = os.path.join(settings.SUITES_DIR,
                                         datetime.strftime(datetime.now(), '%Y%m%d%H%M%S%f'))
        if not os.path.exists(testcase_dir_path):
            os.mkdir(testcase_dir_path)

        env = Envs.objects.filter(id=env_id, is_delete=False).first()
        modulars_objs = Modulars.objects.filter(is_delete=False, project=instance)

        if not modulars_objs.exists():
            data_dict = {
                'detail': '此项目下无功能，无法运行！'
            }
            return Response(data_dict, status=status.HTTP_400_BAD_REQUEST)

        for mo_obj in modulars_objs:
            testcase_objs = Testcases.objects.filter(is_delete=False, modular=mo_obj)
            for one_obj in testcase_objs:
                common.generate_testcase_files(one_obj, env, testcase_dir_path)

        # 运行用例
        return common.run_testcase(instance, testcase_dir_path)

    def get_serializer_class(self):
        if self.action == 'names':
            return serializers.ProjectNameSerializer
        elif self.action == 'run':
            return serializers.ProjectsRunSerializer
        else:
            return self.serializer_class






